home *** CD-ROM | disk | FTP | other *** search
/ Programming Languages Suite / ProgramD2.iso / Borland / Borland C++ V5.02 / BOCOLE.PAK / BCOM.H next >
C/C++ Source or Header  |  1997-05-06  |  7KB  |  202 lines

  1. //----------------------------------------------------------------------------
  2. // ObjectComponents
  3. // Copyright (c) 1994, 1996 by Borland International, All Rights Reserved
  4. //
  5. // $Revision:   2.6  $
  6. //
  7. // Macros and utility stuff for implementing COM support (i.e. IUnknown) in 
  8. // Bolero apps.
  9. //----------------------------------------------------------------------------
  10. #ifndef _BCOM_H
  11. #define _BCOM_H
  12.  
  13. /*
  14.  *                      Include COM definitions
  15.  */
  16.  
  17. #include <string.h>                     // for fmemcmp
  18.  
  19. #ifdef  WIN32
  20.   #ifndef _OBJBASE_H_
  21.     #include <objbase.h>                    // include COM definitions
  22.   #endif
  23.   #ifndef _OLEAUTO_H_
  24.     #include <oleauto.h>
  25.   #endif
  26. #else
  27.   #ifndef __COMPOBJ_H
  28.     #include <compobj.h>                    // include COM definitions
  29.   #endif
  30.   #ifndef __DISPATCH_H
  31.     #include <Dispatch.h>
  32.   #endif
  33. #endif
  34.  
  35. #ifdef INITGUID
  36.         #ifndef WIN32
  37.         #include <coguid.h>             // why do they exclude this?
  38.         #endif
  39. #endif
  40.  
  41. #include "portdefs.h"           // temporarily. portdefs is in transition. (PHP)
  42.  
  43. #ifdef WIN32
  44. #include "pshpack8.h"
  45. #endif
  46.  
  47. #ifdef __BORLANDC__
  48.         #undef NOERROR
  49.         #define NOERROR ((HRESULT) 0L)
  50.         #undef ResultFromScode(sc)
  51.         inline HRESULT ResultFromScode(SCODE sc)
  52.                 {return (HRESULT) (sc & 0x800FFFFFL);}
  53.         #undef GetScode(hr)
  54.         inline SCODE GetScode(HRESULT hr)
  55.                 {return   ((SCODE)(hr) & 0x800FFFFFL); }
  56. #endif
  57.  
  58. // force this and vtable pointers far on interfaces
  59. #ifdef __BORLANDC__
  60.         #define _ICLASS  __HUGE
  61. #else
  62.         #define _ICLASS  FAR
  63. #endif
  64.  
  65. #ifdef WIN32
  66.     #define _IFUNC STDMETHODCALLTYPE
  67. #else
  68.     #define _IFUNC FAR CDECL
  69. #endif
  70.  
  71. #ifndef NULLP
  72.         #define NULLP 0L
  73. #endif
  74.  
  75. #define PREDECLARE_INTERFACE( I )               \
  76.   class _ICLASS I;                                                      \
  77.   typedef const I FAR * PC##I;                  \
  78.   typedef const I FAR & RC##I;                  \
  79.   typedef I FAR * P##I;                                         \
  80.   typedef I FAR & R##I;                                         \
  81.  
  82. #if ((defined __BORLANDC__) && (!defined WIN32))
  83.         #pragma option -po-
  84. #endif
  85.  
  86. typedef IUnknown FAR *  PIUnknown;
  87. PREDECLARE_INTERFACE( IBUnknownMain )
  88.  
  89.  
  90. #if ((defined __BORLANDC__) && (!defined WIN32))
  91.         #pragma option -po.
  92. #endif
  93.  
  94. /*
  95.  *              Aggregation help while using multiple inheritance of interfaces.
  96.  */
  97.  
  98. // IUnknownMain (IUnknown replica forces separate implementation in MI)
  99. //
  100. // QueryInterfaceMain handles IID discrimination and delegation
  101. // to "inner" helper objects.
  102. // AddRefMain and ReleaseMain update a reference count data member.
  103. // And delete the object when the reference count reaches zero.
  104. //
  105. // All other IUnknown's (inherited by other interfaces) simply delegate to
  106. // this IUnknownMain, (or that of an aggregator if one exists).
  107. //
  108. // The layout of IUnknownMain is identical to that of IUnknown and can be
  109. // casted to IUnknown safely.  The names are different to prevent the compiler
  110. // from overriding the implementation when multiple inheritance is used.
  111. //      This is the best way to support aggregation and multiple inheritance
  112. // of interfaces, and requires less indirection than the "nested class"
  113. // approach used by Microsoft's OLE2 samples.
  114. //
  115.  
  116. #if ((defined __BORLANDC__) && (!defined WIN32))
  117.         #pragma option -po-
  118. #endif
  119.  
  120. class _ICLASS IBUnknownMain
  121. {
  122. public:
  123.     virtual HRESULT _IFUNC QueryInterfaceMain(REFIID, LPVOID FAR *) = 0;
  124.     virtual ULONG   _IFUNC AddRefMain() = 0;
  125.     virtual ULONG   _IFUNC ReleaseMain() = 0;
  126. };
  127.  
  128. #if ((defined __BORLANDC__) && (!defined WIN32))
  129.         #pragma option -po.
  130. #endif
  131.  
  132.  
  133. #define DEFINE_IUNKNOWN(pUnkOuter)                                              \
  134.         HRESULT _IFUNC QueryInterface(REFIID iid, void FAR* FAR* pif)   \
  135.                 {return pUnkOuter->QueryInterfaceMain(iid, pif);}               \
  136.         ULONG _IFUNC AddRef() {return pUnkOuter->AddRefMain();}                 \
  137.         ULONG _IFUNC Release(){return pUnkOuter->ReleaseMain();}
  138.  
  139.  
  140. /*
  141.  *      Macros for defining inline QueryInterface implementation that can be
  142.  * called statically from derived classes' QueryInterface
  143.  *
  144.  *      For each interface a global inline function with the interface name
  145.  * prepended (followed by an underscore) is defined to allow
  146.  * each interface to compare its own id and QueryInterface its parents'.
  147.  * This simplifies writing QueryInterface.
  148.  */
  149.  
  150. inline HRESULT _IFUNC IUnknown_QueryInterface(IUnknown FAR *, REFIID iid, LPVOID FAR * pif)
  151. {
  152.         // To avoid handing out different IUnknown pointers for
  153.         // the same Windows Object don't match here.
  154.         // Only match in the main IUnknown in the outermost aggregator.
  155.  
  156.         return ResultFromScode(E_NOINTERFACE);
  157. }
  158.  
  159. #define DEFINE_INLINE_QI(I, P) \
  160. inline HRESULT _IFUNC I##_QueryInterface(I FAR * This, REFIID iid, LPVOID FAR *pif) \
  161. {                                                                                                                                                                       \
  162.         return (iid == IID_##I) ?                                                                                               \
  163.                 (*pif = This), This->AddRef(), NOERROR :                                                                \
  164.                 P##_QueryInterface(This, iid, pif);                                                             \
  165. }
  166.  
  167. #define DEFINE_INLINE_QI2(I, P1, P2) \
  168. inline HRESULT _IFUNC I##_QueryInterface(I FAR* This, REFIID iid, LPVOID FAR* pif) \
  169. {                                            \
  170.   return (iid == IID_##I) ?                  \
  171.     (*pif = This), ((P1*)This)->AddRef(), NOERROR : \
  172.     SUCCEEDED(P1##_QueryInterface(This, iid, pif))? NOERROR :\
  173.     P2##_QueryInterface(This, iid, pif);      \
  174. }
  175.  
  176.  
  177. inline HRESULT _IFUNC IBUnknownMain::QueryInterfaceMain(REFIID iid, LPVOID FAR *pif)
  178. {
  179.         return (iid == IID_IUnknown) ?
  180.                 (*pif = this), AddRefMain(), NOERROR :
  181.                 ResultFromScode(E_NOINTERFACE);
  182. }
  183.  
  184. inline HRESULT _IFUNC IUnknown::QueryInterface(REFIID iid, LPVOID FAR *pif)
  185. {
  186.         return (iid == IID_IUnknown) ?
  187.                 (*pif = this), AddRef(), NOERROR :
  188.                 ResultFromScode(E_NOINTERFACE);
  189. }
  190.  
  191. inline PIBUnknownMain AsPIUnknownMain(PIUnknown pUnk) {return (PIBUnknownMain)pUnk;}
  192. inline PIUnknown AsPIUnknown(PIBUnknownMain pUnk) {return (PIUnknown)pUnk;}
  193.  
  194.  
  195. #ifdef WIN32
  196. #include "poppack.h"
  197. #endif
  198.  
  199. #define  IDS_SAVEOBJ  32900
  200.  
  201. #endif
  202.